/// 融云Token实体模型
/// 
/// 用于封装融云即时通讯的令牌信息
class TokenEntity {
  /// 融云Token
  final String token;
  
  /// 融云用户ID
  final String rongcloudUserId;
  
  /// Token获取时间（时间戳，毫秒）
  final int obtainedAt;

  const TokenEntity({
    required this.token,
    required this.rongcloudUserId,
    required this.obtainedAt,
  });
  
  /// 创建新的 Token 实例，自动设置获取时间
  factory TokenEntity.create({
    required String token,
    required String rongcloudUserId,
  }) {
    return TokenEntity(
      token: token,
      rongcloudUserId: rongcloudUserId,
      obtainedAt: DateTime.now().millisecondsSinceEpoch,
    );
  }

  /// 从 JSON 创建 Token 实体对象
  /// 从extraData中提取融云相关信息
  factory TokenEntity.fromJson(Map<String, dynamic> json) {
    return TokenEntity(
      token: json['token']?.toString() ?? '',
      rongcloudUserId: json['rongcloud_user_id']?.toString() ?? '',
      obtainedAt: json['obtained_at']?.toInt() ?? DateTime.now().millisecondsSinceEpoch,
    );
  }
  
  /// 从extraData创建TokenEntity
  factory TokenEntity.fromExtraData(Map<String, dynamic> extraData) {
    return TokenEntity(
      token: extraData['token']?.toString() ?? '',
      rongcloudUserId: extraData['rongcloud_user_id']?.toString() ?? '',
      obtainedAt: DateTime.now().millisecondsSinceEpoch,
    );
  }

  /// 转换为 JSON 格式
  Map<String, dynamic> toJson() {
    return {
      'token': token,
      'rongcloud_user_id': rongcloudUserId,
      'obtained_at': obtainedAt,
    };
  }

  /// 创建副本，支持部分字段更新
  TokenEntity copyWith({
    String? token,
    String? rongcloudUserId,
    int? obtainedAt,
  }) {
    return TokenEntity(
      token: token ?? this.token,
      rongcloudUserId: rongcloudUserId ?? this.rongcloudUserId,
      obtainedAt: obtainedAt ?? this.obtainedAt,
    );
  }

  /// 判断令牌是否有效
  bool get isValid => token.isNotEmpty && rongcloudUserId.isNotEmpty;

  /// 获取令牌获取时间（DateTime）
  DateTime get obtainedAtDateTime => DateTime.fromMillisecondsSinceEpoch(obtainedAt);

  @override
  String toString() {
    // 为了安全，只显示 token 的前8位和后4位
    final maskedToken = token.length > 12
        ? '${token.substring(0, 8)}...${token.substring(token.length - 4)}'
        : '****';
    return 'TokenEntity(token: $maskedToken, rongcloudUserId: $rongcloudUserId)';
  }

  @override
  bool operator ==(Object other) {
    if (identical(this, other)) return true;
    return other is TokenEntity &&
        other.token == token &&
        other.rongcloudUserId == rongcloudUserId &&
        other.obtainedAt == obtainedAt;
  }

  @override
  int get hashCode => 
      token.hashCode ^ 
      rongcloudUserId.hashCode ^
      obtainedAt.hashCode;
}

